; This module initializes the microcontroller then executes MAIN forever
;
Reset:
MOV SP, #235 ; Initialize the Stack at top of internal memory
MOV PageReg, #7FH ; Needed to use MOVX @Ri
MOV R0, #LOW(USBControl) ; Simulate a disconnect
MOVX A, @R0
ANL A, #11110011b ; Clear DISCON, DISCOE
MOVX @R0, A
CALL Wait100msec ; Give the host time to react
MOVX A, @R0 ; Reconnect with this new identity
ORL A, #00000110b ; Set DISCOE to enable pullup resistor
MOVX @R0, A ; Set RENUM so that 8051 handles USB requests
CLR A
MOV FLAGS, A ; Start in Default state
MOV CurrentConfiguration, A ; This example supports two configurations
MOV R0, #DisplayPosition ; Note LEDBuffer follows DisplayPosition
MOV R7, #43
MOV A, #8 ; Display a horizontal line
ClearDisplay:
MOV @R0, A
INC R0
DJNZ R7, ClearDisplay
InitializeIOSystem: ; This example uses PortA an IN/OUT and
; the lower 4 bits of PortC as OUT
; Assume a pre-existing configuration (ie Dscope)
MOV R0, #LOW(PortA_Config) ; PageReg = 7F = HIGH(PortA_Config)
CLR A
MOVX @R0, A ; No alternate functions
MOV R1, #LOW(PortA_OE)
CPL A ; = 0FFH
MOVX @R1, A ; Enable PortA for Output
MOV R0, #LOW(PortC_Config) ; PageReg = 7F = HIGH(PortC_Config)
MOV R1, #LOW(PortC_OE)
MOVX A, @R0 ; Get current configuration
ANL A, #0F0H
MOVX @R0, A ; No alternate functions on lower nibble
MOVX A, @R1 ; Get current configuration
ORL A, #0FH
MOVX @R1, A ; Enable PortC_Bits[3:0] for Output
MOV R0, #LOW(PortC_Out)
MOVX A, @R0
ANL A, #0F0H
MOVX @R0, A ; Set Bits [3:0] low
InitializeInterruptSystem: ; First initialize the USB level
MOV R0, #LOW(IN07IEN)
MOVX @R0, A ; Disable interrupts from IN Endpoints 0-7
INC R0
MOVX @R0, A ; Disable interrupts from OUT Endpoints 0-7
INC R0
MOV A, #00000011b
MOVX @R0, A ; Enable (Resume, Suspend,) SOF and SUDAV INTs
INC R0
MOV A, #00000001b
MOVX @R0, A ; Enable Auto Vectoring for USB interrupts
MOV R0, #LOW(OUT07IRQ)
MOV A, #0FFH
MOVX @R0, A ; Clear out any pending interrupts
; Now enable the main level
MOV EIE, #00000001b ; Enable INT2 = USB Interrupt (only)
MOV EI, #11000000b ; Enable interrupt subsystem (and Ser1 for Dscope)
; Initialization Complete.
;
MAIN:
NOP ; Not much of a main loop for this example
JMP MAIN ; All actions are initiated by interrupts
; We are a slave, we wait to be told what to do
Wait100msec:
MOV Temp, #100
Wait1msec: ; A delay loop
MOV DPTR, #-1200
More: INC DPTR ; 3 cycles
MOV A, DPL ; + 2
ORL A, DPH ; + 2
JNZ More ; + 3 = 10 cycles x 1200 = 1msec
DJNZ Temp, Wait1msec
RET
ProcessOutputReport: ; A Report has just been received
; See comment re SetConfiguration in DTables.A51
MOV DPTR, #EP0OutBuffer
MOVX A, @DPTR
; The interpretation of the Report is different depending upon the MODE we are in
; MOV A, CurrentConfiguration
CJNE A, #2, TextMode
DOTmode:
; The report is 41 bytes long and is a mode byte then a buffer
MOV DPTR, #EP0OutBuffer+1 ; Point to the Report (after Mode Byte)
MOV R0, #LEDBuffer
MOVX A, @DPTR
MOV R7, #40 ; Have room for 40 Columns
DMLoop: MOVX A, @DPTR ; Update the local buffer
MOV @R0, A
DJNZ R7, DMloop
RET
TextMode:
; The report is 7 characters long and must be translated into a dot pattern
MOV DPS, #1 ; Select the other Data Pointer
MOV DPTR, #EP0OutBuffer+1 ; Point to the Report
MOV R0, #LEDBuffer
MOV R7, #7 ; Have room for 7 characters
ORLoop: MOVX A, @DPTR
JNB ACC.7, Skip1 ; Valid Characters are 20H to 7FH
MOV A, #3FH ; Replace characters > 7FH with ?
Skip1: CLR C
SUBB A, #20H
JNC Skip2
MOV A, #3CH ; Replace characters < 20H with []
Skip2: MOV B, #5
MUL AB ; B = HI((Char-20H)*5), A = LOW
INC DPS ; Swap to "other" DPTR
MOV DPTR, #LookupTable
ADD A, DPL
MOV DPL, A
MOV A, B
ADDC A, DPH
MOV DPH, A ; DPTR now pointing into Lookup Table
MOV R6, #5
LTCopy: MOVX A, @DPTR
MOV @R0, A
INC DPTR
INC R0
DJNZ R6, LTCopy
MOV @R0, #0 ; Put a space between characters
INC R0
INC DPS ; Switch to DPTR1
INC DPTR ; Point to next character in Output Report
DJNZ R7, ORLoop
INC DPS ; Return DPTR to DPTR0
; Fall into CreateInputReport
CreateInputReport:
; The report is 40 bytes long in this example
; It contains the LED Buffer
MOV DPTR, #EP1InBuffer ; Point to the buffer
MOV R0, #LEDBuffer
MOV R7, #40
IRLoop: MOV A, @R0
MOVX @DPTR, A
INC DPTR
INC R0
DJNZ R7, IRLoop
MOV DPTR, #IN1ByteCount
MOV A, #40
MOVX @DPTR, A ; Endpoint 1 now 'armed', next IN will get data
RET
LookupTable: ; Contains the 5 columns of the 7x5 display
DB 00H,00H,00H,00H,00H ; SPACE
DB 00H,00H,7DH,00H,00H ; !
DB 00H,70H,00H,70H,00H ; "
DB 14H,7FH,14H,7FH,14H ; #
DB 12H,2AH,7FH,2AH,24H ; $
DB 62H,64H,08H,13H,23H ; %
DB 36H,49H,55H,22H,05H ; &
DB 00H,50H,60H,00H,00H ; '
DB 00H,1CH,22H,41H,00H ; (
DB 00H,41H,22H,1CH,00H ; )
DB 14H,08H,3EH,08H,14H ; *
DB 08H,08H,3EH,08H,08H ; +
DB 00H,05H,06H,00H,00H ; ,
DB 08H,08H,08H,08H,08H ; -
DB 00H,03H,03H,00H,00H ; .
DB 02H,04H,08H,10H,20H ; /
DB 3EH,45H,49H,51H,3EH ; 0
DB 00H,21H,7FH,01H,00H ; 1
DB 21H,43H,45H,49H,31H ; 2
DB 42H,41H,51H,69H,46H ; 3
DB 0CH,14H,24H,7FH,04H ; 4
DB 72H,51H,51H,51H,4EH ; 5
DB 1EH,29H,49H,49H,06H ; 6
DB 40H,47H,48H,50H,60H ; 7
DB 36H,49H,49H,49H,36H ; 8
DB 30H,49H,49H,4AH,3CH ; 9
DB 00H,33H,33H,00H,00H ; :
DB 00H,65H,66H,00H,00H ; ;
DB 00H,08H,14H,22H,41H ; <
DB 14H,14H,14H,14H,14H ; =
DB 41H,22H,14H,08H,00H ; >
DB 20H,40H,45H,48H,30H ; ?
DB 26H,49H,4FH,41H,3EH ; @
DB 3FH,48H,48H,48H,3FH ; A
DB 7FH,49H,49H,49H,36H ; B
DB 3EH,41H,41H,41H,22H ; C
DB 7FH,41H,41H,22H,1CH ; D
DB 7FH,49H,49H,49H,41H ; E
DB 7FH,48H,48H,48H,40H ; F
DB 3EH,41H,49H,49H,2FH ; G
DB 7FH,08H,08H,08H,7FH ; H
DB 00H,41H,7FH,41H,00H ; I
DB 02H,01H,41H,7EH,40H ; J
DB 7FH,08H,14H,22H,41H ; K
DB 7FH,01H,01H,01H,01H ; L
DB 7FH,20H,18H,20H,7FH ; M
DB 7FH,10H,08H,04H,7FH ; N
DB 3EH,41H,41H,41H,3EH ; O
DB 7FH,48H,48H,48H,30H ; P
DB 3EH,41H,45H,42H,3DH ; Q
DB 7FH,48H,4CH,4AH,31H ; R
DB 31H,49H,49H,49H,46H ; S
DB 40H,40H,7FH,40H,40H ; T
DB 7EH,01H,01H,01H,7EH ; U
DB 7CH,02H,01H,02H,7CH ; V
DB 7EH,01H,0EH,01H,7EH ; W
DB 63H,14H,08H,14H,63H ; X
DB 70H,08H,07H,08H,70H ; Y
DB 43H,45H,49H,51H,61H ; Z
DB 00H,7FH,41H,41H,00H ; [
DB 7FH,41H,41H,41H,7FH ; []
DB 00H,41H,41H,7FH,00H ; ]
DB 10H,20H,40H,20H,10H ; ^
DB 01H,01H,01H,01H,01H ; _
DB 00H,40H,20H,10H,00H ; \
DB 02H,15H,15H,15H,0FH ; a
DB 7FH,09H,11H,11H,0EH ; b
DB 0EH,11H,11H,11H,02H ; c
DB 0EH,11H,11H,09H,7FH ; d
DB 0EH,15H,15H,15H,0CH ; e
DB 08H,3FH,48H,40H,20H ; f
DB 18H,25H,25H,25H,3EH ; g
DB 7FH,08H,10H,10H,0FH ; h
DB 00H,11H,5FH,01H,00H ; i
DB 02H,01H,11H,5EH,00H ; j
DB 7FH,04H,0AH,11H,00H ; k
DB 00H,41H,7FH,01H,00H ; l
DB 1FH,10H,0CH,10H,0FH ; m
DB 1FH,08H,10H,10H,0FH ; n
DB 0EH,11H,11H,11H,0EH ; o
DB 1FH,14H,14H,14H,08H ; p
DB 08H,14H,14H,14H,1FH ; q
DB 1FH,08H,10H,10H,08H ; r
DB 09H,15H,15H,15H,02H ; s
DB 10H,7EH,11H,01H,02h ; t
DB 1EH,01H,01H,01H,1FH ; u
DB 1CH,02H,01H,02H,1CH ; v
DB 1EH,01H,06H,01H,1EH ; w
DB 11H,0AH,04H,0AH,11H ; x
DB 18H,05H,05H,05H,1EH ; y
DB 11H,13H,15H,19H,11H ; z
DB 00H,08H,36H,41H,00H ; {
DB 00H,00H,7FH,00H,00H ; |
DB 00H,41H,36H,08H,00H ; }
DB 08H,08H,2AH,1CH,08H ; ->
DB 08H,1CH,2AH,08H,08H ; <-